from PySide6.QtCore import Qt
from PySide6.QtGui import QColor, QKeyEvent, QPalette
from PySide6.QtWidgets import (
    QApplication,
    QCheckBox,
    QComboBox,
    QLabel,
    QLineEdit,
    QPushButton,
    QVBoxLayout,
    QWidget,
)


class EnhancedFocusLineEdit(QLineEdit):
    def __init__(self, parent=None):
        super().__init__(parent)
        self.focus_locked = False
        self.default_style = self.styleSheet()
        self.locked_style = (
            "background-color: #fffacd;"  # 浅黄色背景
            "border: 2px solid #ff8c00;"  # 橙色边框
            "font-weight: bold;"
        )

        # 状态标签（用于显示当前状态）
        self.status_label = QLabel("焦点未锁定", self)
        self.status_label.setAlignment(Qt.AlignRight | Qt.AlignVCenter)
        self.status_label.setStyleSheet(
            "color: #666; font-size: 10pt; margin-right: 5px;"
        )

        # 调整标签位置
        self.textChanged.connect(self._adjust_status_label)

    def _adjust_status_label(self):
        # 确保状态标签始终在右侧可见
        self.status_label.move(self.width() - self.status_label.width() - 5, 2)

    def resizeEvent(self, event):
        super().resizeEvent(event)
        self._adjust_status_label()

    def setFocusLocked(self, locked: bool):
        self.focus_locked = locked

        if locked:
            self.setStyleSheet(self.locked_style)
            self.status_label.setText("🔒 焦点已锁定")
            self.status_label.setStyleSheet(
                "color: #ff4500; font-size: 10pt; font-weight: bold; margin-right: 5px;"
            )
            self.setFocus()  # 立即获取焦点
        else:
            self.setStyleSheet(self.default_style)
            self.status_label.setText("焦点未锁定")
            self.status_label.setStyleSheet(
                "color: #666; font-size: 10pt; margin-right: 5px;"
            )

    def focusOutEvent(self, event):
        if self.focus_locked:
            event.ignore()
            self.setFocus()
        else:
            super().focusOutEvent(event)

    def keyPressEvent(self, event: QKeyEvent):
        # ESC键解锁焦点
        if event.key() == Qt.Key_Escape and self.focus_locked:
            self.setFocusLocked(False)
            return

        # 锁定状态下拦截Tab键和Shift+Tab
        if self.focus_locked and (
            event.key() == Qt.Key_Tab or event.key() == Qt.Key_Backtab
        ):
            return

        super().keyPressEvent(event)

    def mousePressEvent(self, event):
        # 锁定状态下忽略外部点击（但允许内部点击）
        if self.focus_locked and not self.rect().contains(event.pos()):
            event.ignore()
        else:
            super().mousePressEvent(event)
            if self.focus_locked:
                self.setFocus()


app = QApplication([])
window = QWidget()
window.setWindowTitle("焦点锁定演示")
layout = QVBoxLayout(window)

# 标题标签
title_label = QLabel("焦点锁定功能演示")
title_label.setStyleSheet("font-size: 16pt; font-weight: bold; margin-bottom: 10px;")
title_label.setAlignment(Qt.AlignCenter)

# 说明标签
instruction_label = QLabel("""
1. 点击"启用焦点锁定"按钮后，输入框将无法失去焦点
2. 锁定状态下：
   - 无法通过点击其他控件转移焦点
   - 无法使用Tab键导航
   - 无法通过鼠标点击外部区域转移焦点
3. 按ESC键或点击"禁用焦点锁定"按钮解除锁定
""")
instruction_label.setWordWrap(True)
instruction_label.setAlignment(Qt.AlignLeft)

# 创建可锁定焦点的输入框
locked_edit = EnhancedFocusLineEdit()
locked_edit.setPlaceholderText("在此输入文本...")

# 创建控制按钮
toggle_button = QPushButton("启用焦点锁定")
toggle_button.setCheckable(True)
toggle_button.setStyleSheet("""
    QPushButton { padding: 8px 16px; border-radius: 4px; }
    QPushButton:checked { background-color: #ff4500; color: white; }
""")


# 按钮状态切换事件
def toggle_focus_lock(checked):
    locked_edit.setFocusLocked(checked)
    toggle_button.setText("禁用焦点锁定" if checked else "启用焦点锁定")


toggle_button.toggled.connect(toggle_focus_lock)

# 创建其他控件（用于测试焦点转移）
other_edit = QLineEdit()
other_edit.setPlaceholderText("普通输入框（锁定时无法获取焦点）")

checkbox = QCheckBox("测试复选框")
combobox = QComboBox()
combobox.addItems(["选项1", "选项2", "选项3"])


# 禁用其他控件的焦点（仅在锁定状态下）
def disable_other_focus(locked):
    for widget in [other_edit, checkbox, combobox, toggle_button]:
        if locked:
            widget.setFocusPolicy(Qt.NoFocus)
        else:
            widget.setFocusPolicy(Qt.StrongFocus)


toggle_button.toggled.connect(disable_other_focus)

# 添加所有控件到布局
layout.addWidget(title_label)
layout.addWidget(instruction_label)
layout.addWidget(QLabel("🔒 可锁定焦点的输入框:"))
layout.addWidget(locked_edit)
layout.addWidget(toggle_button)
layout.addWidget(QLabel("\n其他控件（锁定时无法获取焦点）:"))
layout.addWidget(other_edit)
layout.addWidget(checkbox)
layout.addWidget(combobox)

# 底部状态标签
status_label = QLabel("状态: 未锁定")
status_label.setStyleSheet("color: #666; font-size: 10pt; margin-top: 10px;")
layout.addWidget(status_label)


# 更新状态标签
def update_status(locked):
    status_label.setText(f"状态: {'已锁定' if locked else '未锁定'}")
    status_label.setStyleSheet(
        f"color: {'#ff4500' if locked else '#666'}; font-size: 10pt; margin-top: 10px; font-weight: {'bold' if locked else 'normal'};"
    )


toggle_button.toggled.connect(update_status)

# 初始状态
update_status(False)

window.show()
app.exec()
